/**
 * 
 * 微信获取token的入口文件
 * 管理素材接口
 * https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET
 */
const fs = require("fs")
const request = require("request-promise")
const base = 'https://api.weixin.qq.com/cgi-bin/'
const api = {
    accessToken: base + 'token?grant_type=client_credential',
    temporary: {
        upload: base + 'media/upload?'
    },
    permanent: {
        uploadNew: base + 'material/add_news?',
        upload: base + 'material/add_material?',
        uploadNewPic: base + 'material/uploadimg?'
    }
}
module.exports = class Wechat {
    constructor(opts){
        this.opts = Object.assign({},opts)
        this.appID = opts.appID
        this.appSecret = opts.appSecret
        this.getAccessToken = opts.getAccessToken
        this.saveAccessToken = opts.saveAccessToken
        this.fetchAccessToken()
    }
    async request(options){
        options = Object.assign({}, options, {json: true})

        try{
            const res = await request(options)
            return res
        }catch(err){
            console.log(err)
        }
    }


    // 1.首先检查数据库里的token是否过期
    // 2.过期则刷新
    // 3, token入库
    async fetchAccessToken(){
        let data = await this.getAccessToken()
        
        if(!this.isValidToken(data)){
            data = await this.updateAccessToken()
        }
        await this.saveAccessToken(data)
        return data
    }
    // 获取token
    async updateAccessToken () {
        const url = api.accessToken + `&appid=${this.appID}&secret=${this.appSecret}`

        const data =await this.request({url})
        const now = new Date().getTime()
        const expiresIn = now + (data.expires_in - 20) * 1000

        data.expires_in = expiresIn
        return data
    }

    isValidToken(data){
        if(!data || !data.expires_in){
            return false
        }

        const expiresIn = data.expires_in
        const now = new Date().getTime()
        console.log(now, expiresIn)
        if(now < expiresIn){
            return true
        } else {
            return false
        }
    }

    uploadMaterial(token, type, meterial, permanent = false){
        let form = {}
        let url = api.temporary.upload

        // 永久素材 继承外面传入的新对象
        if(permanent){
            url = api.permanent.upload

            form = Object.assign(form, permanent)
        }

        // 上传图文消息的图片素材
        if(type == 'pic'){
            url = api.permanent.uploadNewPic
        }

        // 图文非图文的素材提交表单的切换
        if(type == 'news'){
            url = api.permanent.uploadNew
            form = meterial
        } else {
            form.media = fs.createReadStream(meterial)
        }

        // form.media = fs.createReadStream(meterial)
        let uploadUrl = `${url}access_token=${token}`
        // 根据素材永久性填充 token
        if(!permanent){
            uploadUrl += `&type=${type}`
        } else {
            if(type !== 'news'){
                form.access_token = token
            }
        }
        const options = {
            method: "POST",
            url: uploadUrl,
            json: true,
            
        }
        // 图文和非图文在request提交主体判断
        if(type === 'news'){
            options.body = form
        } else {
            options.formData = form
        }

        return options
    }


    async handle(operation, ...args){
        const tokenData = await this.fetchAccessToken()
        const options = this[operation](tokenData.access_token, ...args)
        const data = await this.request(options)

        return data
    }
}